package com.woody.aggregate.application.service.msgsendrule.converter;

import com.woody.aggregate.infrastructure.messagebox.dto.MessageboxCountDTO;
import com.woody.aggregate.infrastructure.msgsendrule.dto.MsgSendRuleInfoDTO;
import com.woody.aggregate.infrastructure.msgsendrule.dto.SaveMsgSendRuleDTO;
import com.woody.aggregate.msgsendrule.req.SaveMsgSendRuleReq;
import com.woody.aggregate.msgsendrule.vo.MsgSendRuleInfoVo;
import com.woody.aggregate.msgsendrule.vo.MsgSendRuleVo;

import javax.annotation.Nonnull;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;

/**
 * &copy; All rights Reserved
 *
 * @author wénkǎi.zhāng 2025-03-20
 */
public class MsgSendRuleConverter {

    /**
     *
     * <br />
     * @param ruleList 规则列表
     * @param bindingCounts 规则绑定的弹窗统计数据
     * @return
     */
    public static List<MsgSendRuleVo> convertToVoList(@Nonnull List<MsgSendRuleInfoDTO> ruleList, @Nonnull List<MessageboxCountDTO> bindingCounts) {
        // <规则id, <状态, 该规则状态的弹窗数量>
        Map<Integer, Map<Integer, Integer>> dtoMap = convertToDtoMap(bindingCounts);
        return ruleList.stream()
                .map(rule -> {
                    Map<Integer, Integer> statusCountMap = Optional.ofNullable(dtoMap.get(rule.getId())).orElse(new HashMap<>());
                    return convertToVo(rule, statusCountMap);
                })
                .collect(Collectors.toList());
    }


    /**
     * dto转vo
     * <br />
     * @param rule
     * @return
     */
    public static MsgSendRuleVo convertToVo(MsgSendRuleInfoDTO rule) {
        MsgSendRuleVo vo = new MsgSendRuleVo();
        vo.setRuleId(rule.getId());
        vo.setRuleName(rule.getTitle());
        vo.setCategoryId(rule.getCategoryId());
        vo.setCategoryName(rule.getCategoryName());
        vo.setFrequency(rule.getFrequency());
        vo.setUserScope(rule.getUserScope());
        vo.setUserType(rule.getUserType());
        vo.setStartType(rule.getStartType());
        vo.setStartTime(rule.getStartTime());
        return vo;
    }


    /**
     * dto转vo，返回的vo对象包含规则绑定的弹窗数量
     * <br />
     * @param rule
     * @param statusCountMap
     * @return
     */
    public static MsgSendRuleVo convertToVo(MsgSendRuleInfoDTO rule, Map<Integer, Integer> statusCountMap) {
        MsgSendRuleVo vo = convertToVo(rule);
        if (statusCountMap != null) {
            // 规则绑定的弹窗总数
            int bindingTotal = statusCountMap.values().stream().mapToInt(Integer::intValue).sum();
            // 规则绑定的已启用弹窗数量
            int enabledCount = Optional.ofNullable(statusCountMap.get(1)).orElse(0);

            vo.setBindingsTotal(bindingTotal);
            vo.setEnabledBindingsCount(enabledCount);
        }

        return vo;
    }


    /**
     * dto转vo
     * <br />
     * @param rule
     * @return
     */
    public static MsgSendRuleInfoVo convertToInfoVo(MsgSendRuleInfoDTO rule) {
        MsgSendRuleInfoVo vo = new MsgSendRuleInfoVo();
        vo.setRuleId(rule.getId());
        vo.setRuleName(rule.getTitle());
        vo.setCategoryId(rule.getCategoryId());
        vo.setCategoryName(rule.getCategoryName());
        vo.setFrequency(rule.getFrequency());
        vo.setUserScope(rule.getUserScope());
        vo.setUserType(rule.getUserType());
        vo.setStartType(rule.getStartType());
        vo.setStartTime(rule.getStartTime());
        return vo;
    }

    /**
     * 创建、编辑规则的请求参数，转换为统一的数据对象
     * <br />
     * @param request
     * @return
     */
    public static SaveMsgSendRuleDTO convertToSaveDto(SaveMsgSendRuleReq request) {
        SaveMsgSendRuleDTO saveDto = new SaveMsgSendRuleDTO();
        saveDto.setRuleName(request.getRuleName());
        saveDto.setCategoryId(request.getCategoryId());
        saveDto.setFrequency(request.getFrequency());
        saveDto.setUserScope(request.getUserScope());
        saveDto.setUserType(request.getUserType());
        saveDto.setStartType(request.getStartType());
        saveDto.setStartTime(request.getStartTime());
        saveDto.setOperatorUserId(request.getOperatorUserId());
        return saveDto;

    }

    private static Map<Integer, Map<Integer, Integer>> convertToDtoMap(List<MessageboxCountDTO> bindingCounts) {
        return bindingCounts.stream()
                .collect(Collectors.groupingBy(
                        MessageboxCountDTO::getRuleId,
                        Collectors.toMap(MessageboxCountDTO::getStatus, MessageboxCountDTO::getNum, Integer::sum)
                ));
    }
}
